package com.zw.cloud.influxdb.controller;
import java.math.BigDecimal;

import com.zw.cloud.common.utils.DateTimeUtils;
import com.zw.cloud.influxdb.entity.MonitorDeviceTargetAlertFlink;
import com.zw.cloud.influxdb.entity.MonitorDeviceTopDTO;
import com.zw.cloud.influxdb.service.InfluxdbQueryService;
import lombok.extern.slf4j.Slf4j;
import org.influxdb.InfluxDB;
import org.influxdb.dto.BatchPoints;
import org.influxdb.dto.Point;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.PathVariable;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;

import java.time.Instant;
import java.time.LocalDateTime;
import java.time.ZoneOffset;
import java.util.*;

@Slf4j
@RestController
@RequestMapping("/influxdb/monitor")
public class MonitorDeviceTargetAlertFlinkController {

    @Autowired
    private InfluxDB influxDBClient;
    @Autowired
    private InfluxdbQueryService influxdbQueryService;

    /**
     * 批量插入
     */
    @GetMapping("/batchInsert/{orgCode}/{deviceId}/{minusMinutes}")
    //http://localhost:10010/influxdb/monitor/batchInsert/devController/3/10
    public void batchInsert(@PathVariable String orgCode,@PathVariable String deviceId, @PathVariable Integer minusMinutes) {
        LocalDateTime now = LocalDateTime.now();
        List<MonitorDeviceTargetAlertFlink> alertFlinkList = new ArrayList<>();
        for (int i = 0; i < minusMinutes; i++) {
            BigDecimal bigDecimal = BigDecimal.valueOf(33);
            MonitorDeviceTargetAlertFlink alertFlink = buildMonitorDeviceTargetAlertFlink(orgCode,deviceId,bigDecimal.add(BigDecimal.valueOf(i)), now.minusMinutes(i));
            alertFlinkList.add(alertFlink);
        }
        alertFlinkList.sort(Comparator.comparing(MonitorDeviceTargetAlertFlink::getTime));
        BatchPoints.Builder builder = BatchPoints.builder();
        alertFlinkList.forEach(m -> builder.point(Point.measurementByPOJO(m.getClass()).addFieldsFromPOJO(m).build()));
        //写入
        influxDBClient.write(builder.build());
    }

    /**
     * 获取数据
     */
    @GetMapping("/queryList/{startTimeStr}/{endTimeStr}/{orgCode}")
    //http://localhost:10010/influxdb/monitor/queryList/2024-02-28%2011:00:00/2024-02-28%2012:00:00/3983D94F788342E1B0D8F52EA890D8E8
    public List<MonitorDeviceTargetAlertFlink> queryList(@PathVariable String startTimeStr, @PathVariable String endTimeStr, @PathVariable String orgCode){
        String sql = "SELECT * FROM monitor_device_target_alert_flink where time >= $startTime and time <= $endTime and orgCode = $orgCode order by time desc limit 20;";
        LocalDateTime startTime = DateTimeUtils.parse2datetime(startTimeStr, DateTimeUtils.DATE_TIME_PATTERN);
        LocalDateTime endTime = DateTimeUtils.parse2datetime(endTimeStr, DateTimeUtils.DATE_TIME_PATTERN);
        Map<String, Object> bindParams = new HashMap<>();
        bindParams.put("startTime", startTime);
        bindParams.put("endTime", endTime);
        bindParams.put("orgCode",orgCode);
        return influxdbQueryService.queryDeviceReportData(sql,MonitorDeviceTargetAlertFlink.class,bindParams);
    }

    /**
     * groupBy
     */
    @GetMapping("/groupBy/{startTimeStr}/{endTimeStr}/{orgCode}")
    //http://localhost:10010/influxdb/monitor/groupBy/2024-03-13%2018:00:00/2024-03-13%2019:00:00/devController
    public List<MonitorDeviceTopDTO> groupBy(@PathVariable String startTimeStr, @PathVariable String endTimeStr, @PathVariable String orgCode){
        String sql = "SELECT count(deviceName) as count FROM monitor_device_target_alert_flink\n" +
                "WHERE alertStartTime >= $startTime and alertStartTime <= $endTime and orgCode = $orgCode GROUP BY deviceId";
        LocalDateTime startTime = DateTimeUtils.parse2datetime(startTimeStr, DateTimeUtils.DATE_TIME_PATTERN);
        LocalDateTime endTime = DateTimeUtils.parse2datetime(endTimeStr, DateTimeUtils.DATE_TIME_PATTERN);
        Map<String, Object> bindParams = new HashMap<>();
        bindParams.put("startTime", startTime.getSecond());
        bindParams.put("endTime", endTime.getSecond());
        bindParams.put("orgCode",orgCode);
        return influxdbQueryService.queryData(sql,MonitorDeviceTopDTO.class,bindParams,"monitor_device_target_alert_flink");
    }

    private MonitorDeviceTargetAlertFlink buildMonitorDeviceTargetAlertFlink(String orgCode,String deviceId,BigDecimal value, LocalDateTime localDateTime) {
        Long second = localDateTime.toEpochSecond(ZoneOffset.of("+8"));
        Instant instant = Instant.ofEpochSecond(second);

        MonitorDeviceTargetAlertFlink monitorDeviceTargetAlertFlink = new MonitorDeviceTargetAlertFlink();
        monitorDeviceTargetAlertFlink.setTime(instant);
        monitorDeviceTargetAlertFlink.setOrgCode(orgCode);
        monitorDeviceTargetAlertFlink.setDeviceId(deviceId);
        monitorDeviceTargetAlertFlink.setTargetCode("lowerFeed");
        monitorDeviceTargetAlertFlink.setActuallyValue(value);
        monitorDeviceTargetAlertFlink.setAlertLevel(0L);
        monitorDeviceTargetAlertFlink.setAlertRemoveTime(0L);
        monitorDeviceTargetAlertFlink.setAlertStartTime(second);
        monitorDeviceTargetAlertFlink.setAlertType("d27");
        monitorDeviceTargetAlertFlink.setAlertTypeName("下超喂");
        monitorDeviceTargetAlertFlink.setCtime(second);
        monitorDeviceTargetAlertFlink.setDeviceCode("004");
        monitorDeviceTargetAlertFlink.setDeviceName("定型机2");
        monitorDeviceTargetAlertFlink.setIcCard("231106222");
        monitorDeviceTargetAlertFlink.setIotCode("8888");
        monitorDeviceTargetAlertFlink.setSettingVal(false);
        monitorDeviceTargetAlertFlink.setRecommendValue(new BigDecimal("40"));
        monitorDeviceTargetAlertFlink.setSettingValue(new BigDecimal("50"));
        return monitorDeviceTargetAlertFlink;

    }


}
